/**
 * 在前面 12_泛型_3、条件类型.ts 中，已经简单介绍过条件类型，下面继续介绍一下：
 * 
 * 条件类型的语法类似于平时常用的 三元表达式，
 * 
 * 条件类型中使用 extends 判断类型的兼容性，而非判断类型的全等性：
 * 这是因为在类型层面中，对于能够 进行赋值操作 的两个变量，并不需要它们的类型完全相等，只需要具有兼容性
*/

//1、条件类型绝大部分场景下会和泛型一起使用：
type LiteralType<T> = T extends string ? "string" : "other";
type Res1 = LiteralType<"hanxuming">; // "string"
type Res2 = LiteralType<599>; // "other"

//2、在函数中，条件类型与泛型的搭配同样很常见
//当调用这个函数时，由于两个参数都引用了泛型参数 T ，因此泛型会被填充为一个 联合类型：
function universalAdd<T extends number | bigint | string>(x: T, y: T) {
    return x + (y as any);
}
universalAdd(599, 1); // T 填充为 599 | 1
universalAdd("hanxuming", "599"); // T 填充为 hanxuming | 599

//3、条件类型还可以用来对 更复杂的类型 进行比较，比如 函数类型：
type Func = (...args: any[]) => any;
type FunctionConditionType<T extends Func> = T extends (...args: any[]) => string
  ? 'A string return func!'
  : 'A non-string return func!';
//  "A string return func!"
type StringResult = FunctionConditionType<() => string>;
// 'A non-string return func!';
type NonStringResult1 = FunctionConditionType<() => boolean>;
// 'A non-string return func!';
type NonStringResult2 = FunctionConditionType<() => number>;

//export {}：解决“无法重新声明块范围变量”错误提示问题
export { }